package com.truthbean.log.slf4j;

import com.truthbean.log.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.Marker;
import org.slf4j.MarkerFactory;
import org.slf4j.helpers.MarkerIgnoringBase;
import org.slf4j.spi.LocationAwareLogger;

/**
 * @author TruthBean
 * @since 0.0.1
 * Created on 2018-02-01 22:31.
 */
public class Slf4jImpl implements Logger {
    /**
     * this class name
     */
    private static final String CALLER_FQCN = Slf4jImpl.class.getName();

    /**
     * logger using this class
     */
    private static final org.slf4j.Logger TEST_LOGGER = LoggerFactory.getLogger(Slf4jImpl.class);

    private static boolean isTest = false;

    /**
     * test TEST_LOGGER class
     */
    static {
        if (!(TEST_LOGGER instanceof LocationAwareLogger)) {
            isTest = true;
            TEST_LOGGER.error(TEST_LOGGER.getClass() + " is not a suitable logger");
        }
    }

    /**
     * slf4j location aware logger
     */
    private LocationAwareLogger log;

    private MarkerIgnoringBase testLogger;

    /**
     * marker
     */
    private static final Marker MARKER = MarkerFactory.getMarker(com.truthbean.log.LoggerFactory.MARKER);

    public Slf4jImpl() {
    }

    public Slf4jImpl(LocationAwareLogger log) {
        this.log = log;
    }

    public Slf4jImpl(MarkerIgnoringBase testLogger) {
        this.testLogger = testLogger;
    }

    @Override
    public void info(String msg) {
        if (isTest) {
            testLogger.info(MARKER, msg);
        } else {
            this.log.log(MARKER, CALLER_FQCN, LocationAwareLogger.INFO_INT, msg, null, null);
        }
    }

    @Override
    public void info(String msg, Object... param) {
        if (isTest) {
            testLogger.info(MARKER, msg, param);
        } else {
            this.log.log(MARKER, CALLER_FQCN, LocationAwareLogger.INFO_INT, msg, param, null);
        }
    }

    @Override
    public void debug(String msg) {
        if (isTest) {
            testLogger.debug(MARKER, msg);
        } else {
            this.log.log(MARKER, CALLER_FQCN, LocationAwareLogger.DEBUG_INT, msg, null, null);
        }
    }

    @Override
    public void debug(String msg, Object... param) {
        if (isTest) {
            testLogger.debug(MARKER, msg, param);
        } else {
            this.log.log(MARKER, CALLER_FQCN, LocationAwareLogger.DEBUG_INT, msg, param, null);
        }
    }

    @Override
    public void error(String msg, Throwable e) {
        if (isTest) {
            testLogger.error(MARKER, msg, e);
        } else {
            this.log.log(MARKER, CALLER_FQCN, LocationAwareLogger.ERROR_INT, msg, null, e);
        }
    }

    @Override
    public void setClass(Class<?> clazz) {
        setClassName(clazz.getName());
    }

    @Override
    public void setClassName(String className) {
        if (isTest) {
            this.testLogger = (MarkerIgnoringBase) LoggerFactory.getLogger(className);
        } else {
            this.log = (LocationAwareLogger) LoggerFactory.getLogger(className);
        }
    }
}
